{
 "cells": [
  {
   "cell_type": "code",
   "execution_count": 2,
   "metadata": {},
   "outputs": [],
   "source": [
    "from numba import cuda\n",
    "import numpy as np\n",
    "from numba import jit,float32,int64,int8,float64,njit,prange\n",
    "import math\n",
    "import time"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 15,
   "metadata": {},
   "outputs": [],
   "source": [
    "def PathGeneration(numSims,N,S,r,v,dt):\n",
    "    z =np.random.normal(size=(numSims,N))\n",
    "    z[:,0]=0\n",
    "    z=np.cumsum(z,axis=1)\n",
    "    path=np.tile(np.arange(0,N,1),(numSims,1))\n",
    "    ST=S*np.exp((r-0.5*v**2)*dt*path+v*np.sqrt(dt)*z)\n",
    "    return ST\n",
    "\n",
    "def main():\n",
    "    \n",
    "    koDates = np.array([30*(i+1) for i in range(12)])\n",
    "    kiDates = np.array([i for i in range(360)])\n",
    "    S_list = [100+i for i in range(1)]\n",
    "    HLow = 80\n",
    "    HHigh = 103\n",
    "    KLow = 100\n",
    "    rCoupon = 0.1\n",
    "    rMaturity = 0.1\n",
    "\n",
    "    # 交易日个数\n",
    "    N = 361\n",
    "    T = 1\n",
    "    r = 0.025\n",
    "    b = 0\n",
    "    v =0.1\n",
    "    dt=T/N\n",
    "\n",
    "    numSims =int(1e5)\n",
    "    S=100\n",
    "    ST=PathGeneration(numSims,N,S,r,v,dt)\n",
    "    n=ST.shape[0]\n",
    "    ST_device=cuda.to_device(ST)\n",
    "    ko_device=cuda.to_device(koDates)\n",
    "    ki_device=cuda.to_device(kiDates)\n",
    "    knockOut=np.zeros(n)\n",
    "    knockOut=cuda.to_device(knockOut)\n",
    "    doubleNoTouch=np.zeros(n)\n",
    "    doubleNoTouch=cuda.to_device(doubleNoTouch)\n",
    "    knockin=np.zeros(n)\n",
    "    knockin=cuda.to_device(knockin)\n",
    "    SeperatePrice_func[10000,1024](ST,koDates,kiDates,HHigh,HLow,rCoupon,N,r,rMaturity,T,KLow,numSims,dt,knockOut,doubleNoTouch,knockin)\n",
    "    cuda.synchronize()\n",
    "    knockOut=knockOut.copy_to_host()\n",
    "    doubleNoTouch=doubleNoTouch.copy_to_host()\n",
    "    knockin=knockin.copy_to_host()\n",
    "    print(knockOut)\n",
    "    knockOutPrice=np.sum(knockOut)/numSims\n",
    "    doubleNoTouchPrice=np.sum(doubleNoTouch)/numSims\n",
    "    knockinPrice=np.sum(knockin)/numSims\n",
    "    print('敲出价值{}'.format(knockOutPrice))\n",
    "    print('不敲入不敲出价值{}'.format(doubleNoTouchPrice))\n",
    "    print('敲入价值{}'.format(knockinPrice))\n",
    "\n",
    "    \n",
    "@cuda.jit\n",
    "def SeperatePrice_func(ST,koDates,kiDates,HHigh,HLow,rCoupon,N,r,rMaturity,T,KLow,numSims,dt,knockOut,doubleNoTouch,knockin):\n",
    "    i=cuda.threadIdx.x+cuda.blockDim.x*cuda.blockIdx.x\n",
    "    print(i)\n",
    "    if i<ST.shape[0]:\n",
    "        path=ST[i]\n",
    "        koDate=-1\n",
    "        kiDate=0\n",
    "        for i in koDates:\n",
    "            if path[i]>HHigh:\n",
    "                koDate=i\n",
    "                kiState=0\n",
    "                break\n",
    "        if koDate==-1:\n",
    "            for i in kiDates:\n",
    "                if path[i]<=HLow:\n",
    "                    koDate=-1\n",
    "                    kiState=1\n",
    "                    break\n",
    "        knockOut[i]=KnockOutPrice_func(koDate,rCoupon,dt,r)\n",
    "        doubleNoTouch[i]=DoubleNoTouchPrice_func(kiState,koDate,rMaturity,r,T)\n",
    "        knockin[i]=KnockInNotOut_func(kiState,path,KLow,N,r,T)\n",
    "\n",
    "@cuda.jit(device=True)\n",
    "def KnockOutPrice_func(koDate,rCoupon,dt,r):\n",
    "    if koDate>=0:\n",
    "        return rCoupon*(koDate+1)*dt*math.exp(-r*(koDate+1)*dt)\n",
    "    else:\n",
    "        return 0\n",
    "        \n",
    "@cuda.jit(device=True)\n",
    "def DoubleNoTouchPrice_func(kiState,koDate,rMaturity,r,T):\n",
    "    if kiState==0 and koDate==0:\n",
    "        return rMaturity*math.exp(-r*T)\n",
    "    else:\n",
    "        return 0\n",
    "\n",
    "@cuda.jit(device=True)\n",
    "def KnockInNotOut_func(kiState,path,KLow,N,r,T):\n",
    "    if kiState==1:\n",
    "        return min(-(KLow-path[-1])/path[0],0)*math.exp(-r*T)\n",
    "    else:\n",
    "        return 0\n",
    "        "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "main()"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "@cuda.jit(parallel=True,fastmath=True,nogil=True,cache=True)\n",
    "def SeperatePrice_func(ST,koObservationDates,kiObservationDates,HHigh,HLow,rCoupon,N,r,rMaturity,T,KLow,numSims,dt):\n",
    "    n=ST.shape[0]\n",
    "    S=ST[0,0]\n",
    "    knockOut=np.zeros(shape=(n))\n",
    "    doubleNoTouch=np.zeros(shape=(n))\n",
    "    knockin=np.zeros(shape=(n))\n",
    "    for i in prange(n):\n",
    "        path=ST[i]\n",
    "        \n",
    "        #判断是否敲出和敲出日期\n",
    "        koDate=-1\n",
    "        kiDate=0\n",
    "        for i in koObservationDates:\n",
    "            if path[i]>HHigh:\n",
    "                koDate=flag\n",
    "                kiState=0\n",
    "                break\n",
    "        if koDate==-1:\n",
    "            for i in kiObservationDates:\n",
    "                if path[i]<=HLow:\n",
    "                    koDate=-1\n",
    "                    kiState=1\n",
    "                    break\n",
    " \n",
    "        knockOut[i]=KnockOutPrice_func(koDate,S,rCoupon,dt,r)\n",
    "        doubleNoTouch[i]=DoubleNoTouchPrice_func(kiState,koDate,rMaturity,r,T)\n",
    "        knockin[i]=KnockInNotOut_func(kiState,path,KLow,N,r,T)\n",
    "    knockOutPrice=np.sum(knockOut)/numSims\n",
    "    doubleNoTouchPrice=np.sum(doubleNoTouch)/numSims\n",
    "    knockinPrice=np.sum(knockin)/numSims\n",
    "    return knockOutPrice,doubleNoTouchPrice,knockinPrice\n",
    "\n",
    "@cuda.jit(float64(int64,float64,float64,float64,float64),nopython=True,fastmath=True,cache=True)\n",
    "def KnockOutPrice_func(koDate,S,rCoupon,dt,r,knockOutPrice,i):\n",
    "    if koDate>=0:\n",
    "        knockOut[i]=rCoupon*(koDate+1)*dt*np.exp(-r*(koDate+1)*dt)\n",
    "    else:\n",
    "        knockOut[i]=0\n",
    "        \n",
    "@cuda.jit(float64(int64,int64,float64,float64,float64),nopython=True,cache=True)\n",
    "def DoubleNoTouchPrice_func(kiState,koDate,rMaturity,r,T,doubleNoTouch,i):\n",
    "    if kiState==0 and koDate==0:\n",
    "        doubleNoTouch[i]=rMaturity*np.exp(-r*T)\n",
    "    else:\n",
    "        doubleNoTouch[i]=0\n",
    "\n",
    "@cuda.jit(nopython=True,fastmath=True,cache=True)\n",
    "def KnockInNotOut_func(kiState,path,KLow,N,r,T,knockin,i):\n",
    "    if kiState==1:\n",
    "        knockin[i]=min(-(KLow-path[-1])/path[0],0)*np.exp(-r*T)\n",
    "    else:\n",
    "        knockin[i]=0"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 4,
   "metadata": {},
   "outputs": [
    {
     "ename": "TypeError",
     "evalue": "CUDA kernel must have void return type.",
     "output_type": "error",
     "traceback": [
      "\u001b[1;31m---------------------------------------------------------------------------\u001b[0m",
      "\u001b[1;31mTypeError\u001b[0m                                 Traceback (most recent call last)",
      "\u001b[1;32m<ipython-input-4-ec03108ef8ae>\u001b[0m in \u001b[0;36m<module>\u001b[1;34m\u001b[0m\n\u001b[0;32m      9\u001b[0m     \u001b[1;32mreturn\u001b[0m \u001b[1;36m0\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m     10\u001b[0m \u001b[1;33m\u001b[0m\u001b[0m\n\u001b[1;32m---> 11\u001b[1;33m \u001b[1;33m@\u001b[0m\u001b[0mcuda\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mjit\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mfloat64\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mint64\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mfloat64\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mfloat64\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mfloat64\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mfloat64\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mnopython\u001b[0m\u001b[1;33m=\u001b[0m\u001b[1;32mTrue\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mfastmath\u001b[0m\u001b[1;33m=\u001b[0m\u001b[1;32mTrue\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mcache\u001b[0m\u001b[1;33m=\u001b[0m\u001b[1;32mTrue\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0m\u001b[0;32m     12\u001b[0m \u001b[1;32mdef\u001b[0m \u001b[0mKnockOutPrice_func\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mkoDate\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mS\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mrCoupon\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mdt\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mr\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m:\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m     13\u001b[0m     \u001b[1;32mif\u001b[0m \u001b[0mkoDate\u001b[0m\u001b[1;33m>=\u001b[0m\u001b[1;36m1\u001b[0m\u001b[1;33m:\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n",
      "\u001b[1;32m~\\Anaconda3\\1\\lib\\site-packages\\numba\\cuda\\decorators.py\u001b[0m in \u001b[0;36mjit\u001b[1;34m(func_or_sig, argtypes, device, inline, bind, link, debug, **kws)\u001b[0m\n\u001b[0;32m     88\u001b[0m \u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m     89\u001b[0m         \u001b[1;32mif\u001b[0m \u001b[0mrestype\u001b[0m \u001b[1;32mand\u001b[0m \u001b[1;32mnot\u001b[0m \u001b[0mdevice\u001b[0m \u001b[1;32mand\u001b[0m \u001b[0mrestype\u001b[0m \u001b[1;33m!=\u001b[0m \u001b[0mtypes\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mvoid\u001b[0m\u001b[1;33m:\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[1;32m---> 90\u001b[1;33m             \u001b[1;32mraise\u001b[0m \u001b[0mTypeError\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;34m\"CUDA kernel must have void return type.\"\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0m\u001b[0;32m     91\u001b[0m \u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m     92\u001b[0m         \u001b[1;32mdef\u001b[0m \u001b[0mkernel_jit\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mfunc\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m:\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n",
      "\u001b[1;31mTypeError\u001b[0m: CUDA kernel must have void return type."
     ]
    }
   ],
   "source": [
    "@cuda.jit(nopython=True,nogil=True,cache=True)\n",
    "def Knock_func(path,koObservationDates,kiObservationDates,HHigh,HLow):\n",
    "    for i in koObservationDates:\n",
    "        if path[i]>HHigh:\n",
    "            return i\n",
    "    for i in kiObservationDates:\n",
    "        if path[i]<=HLow:\n",
    "            return -1\n",
    "    return 0\n",
    "\n",
    "@cuda.jit(float64(int64,float64,float64,float64,float64),nopython=True,fastmath=True,cache=True)\n",
    "def KnockOutPrice_func(koDate,S,rCoupon,dt,r):\n",
    "    if koDate>=1:\n",
    "        return rCoupon*(koDate+1)*dt*np.exp(-r*(koDate+1)*dt)\n",
    "    else:\n",
    "        return 0\n",
    "\n",
    "@cuda.jit(float64(int64,int64,float64,float64,float64),nopython=True,cache=True)\n",
    "def DoubleNoTouchPrice_func(kiState,koDate,rMaturity,r,T):\n",
    "    if kiState==0 and koDate==0:\n",
    "        return rMaturity*np.exp(-r*T)\n",
    "    else:\n",
    "        return 0\n",
    "\n",
    "@cuda.jit(nopython=True,fastmath=True,cache=True)\n",
    "def KnockInNotOut_func(kiState,path,KLow,N,r,T):\n",
    "    if kiState==1:\n",
    "        return min(-(KLow-path[-1])/path[0],0)*np.exp(-r*T)\n",
    "    else:\n",
    "        return 0\n",
    "\n",
    "@cuda.jit(parallel=True,fastmath=True,nogil=True,cache=True)\n",
    "def SeperatePrice_func(ST,koObservationDates,kiObservationDates,HHigh,HLow,rCoupon,N,r,rMaturity,T,KLow,numSims,dt):\n",
    "    n=ST.shape[0]\n",
    "    S=ST[0,0]\n",
    "    knockOut=np.zeros(shape=(n))\n",
    "    doubleNoTouch=np.zeros(shape=(n))\n",
    "    knockin=np.zeros(shape=(n))\n",
    "    for i in prange(n):\n",
    "        path=ST[i]\n",
    "        flag=Knock_func(path,koObservationDates,kiObservationDates,HHigh,HLow)\n",
    "        if flag>=1:\n",
    "            koDate=flag\n",
    "            kiState=0\n",
    "        elif flag==0:\n",
    "            koDate=0\n",
    "            kiState=0\n",
    "        else:\n",
    "            koDate=0\n",
    "            kiState=1\n",
    "    \n",
    "        knockOut[i]=KnockOutPrice_func(koDate,S,rCoupon,dt,r)\n",
    "        doubleNoTouch[i]=DoubleNoTouchPrice_func(kiState,koDate,rMaturity,r,T)\n",
    "        knockin[i]=KnockInNotOut_func(kiState,path,KLow,N,r,T)\n",
    "    knockOutPrice=np.sum(knockOut)/numSims\n",
    "    doubleNoTouchPrice=np.sum(doubleNoTouch)/numSims\n",
    "    knockinPrice=np.sum(knockin)/numSims\n",
    "    return knockOutPrice,doubleNoTouchPrice,knockinPrice\n",
    "\n",
    "class monte_carlo(object):\n",
    "    def __init__(self, S, T, r, v, N,ds,numSims):\n",
    "        self.S = cuda.to_device(S)\n",
    "        self.ds=cuda.to_device(ds)\n",
    "        self.r = cuda.to_device(r)\n",
    "        self.v = cuda.to_device(v)\n",
    "        self.N = cuda.to_device(N)\n",
    "        self.T=cuda.to_device(T)\n",
    "        self.numSims = cuda.to_device(numSims)\n",
    "        self.dt = cuda.to_device(float(T / N))\n",
    "        self.PathGeneration()\n",
    "\n",
    "    def PathGeneration(self):\n",
    "        z =np.random.normal(size=(self.numSims,self.N))\n",
    "        z[:,0]=0\n",
    "        z=np.cumsum(z,axis=1)\n",
    "        self.z=z\n",
    "        path=np.tile(np.arange(0,self.N,1),(self.numSims,1))\n",
    "        self.path=path\n",
    "        self.ST=self.S*np.exp((self.r-0.5*self.v**2)*self.dt*self.path+self.v*np.sqrt(self.dt)*self.z)\n",
    "        ST_device=cuda.to_device(self.ST)\n",
    "        return self.ST\n",
    "\n",
    "    def PayOffPricer(self,path_df):\n",
    "        pass \n",
    "\n",
    "    def PayOffPricertplus(self, path_df):\n",
    "        pass\n",
    "\n",
    "    def PayOffPricertminus(self, path_df):\n",
    "        pass\n",
    "\n",
    "    def OptionPrice(self):\n",
    "        self.S_optionPrice=self.PayOffPricer(self.ST)\n",
    "        return self.S_optionPrice\n",
    "        \n",
    "    def CallDelta(self):\n",
    "        self.SM=self.ST*(self.S-self.ds)/self.S\n",
    "        self.SP=self.ST*(self.S+self.ds)/self.S\n",
    "        if not hasattr(self,'SP_optionPrice'):\n",
    "            self.SP_optionPrice=self.PayOffPricer(self.SP)\n",
    "        if not hasattr(self,'SM_optionPrice'):\n",
    "            self.SM_optionPrice =self.PayOffPricer(self.SM)\n",
    "        self.callDelta = (self.SP_optionPrice - self.SM_optionPrice) / (self.ds * 2)\n",
    "        return self.callDelta\n",
    "\n",
    "    def OptionGamma(self):\n",
    "        self.SM=self.ST*(self.S-self.ds)/self.S\n",
    "        self.SP=self.ST*(self.S+self.ds)/self.S\n",
    "        if not hasattr(self,'SP_optionPrice'):\n",
    "            self.SP_optionPrice=self.PayOffPricer(self.SP)\n",
    "        if not hasattr(self,'SM_optionPrice'):\n",
    "            self.SM_optionPrice =self.PayOffPricer(self.SM)\n",
    "        if not hasattr(self,'S_optionPrice'):\n",
    "            self.S_optionPrice=self.PayOffPricer(self.ST)\n",
    "        self.Gamma = (self.SP_optionPrice - 2 * self.S_optionPrice + self.SM_optionPrice) / (self.ds * self.ds)\n",
    "        return self.Gamma\n",
    "\n",
    "    def Vega(self):\n",
    "        self.S_sigmaup=self.S*np.exp((self.r-0.5*(self.v*(1+0.1))**2)*self.dt*self.path+(self.v*(1+0.1))*np.sqrt(self.dt)*self.z)\n",
    "        self.S_sigmadown=self.S*np.exp((self.r-0.5*(self.v*(1-0.1))**2)*self.dt*self.path+(self.v*(1-0.1))*np.sqrt(self.dt)*self.z)\n",
    "        self.sigmam_optionPrice =self.PayOffPricer(self.S_sigmadown)\n",
    "        self.sigmap_optionPrice =self.PayOffPricer(self.S_sigmaup)\n",
    "        self.vega = (self.sigmap_optionPrice-self.sigmam_optionPrice)/(0.2*self.v)\n",
    "        return self.vega\n",
    "\n",
    "    def Theta(self):\n",
    "        self.S_Tplus =self.S*np.exp((self.r-0.5*(self.v)**2)*self.dtp*self.path+(self.v)*np.sqrt(self.dtp)*self.z)\n",
    "        self.S_Tminus = self.S * np.exp((self.r - 0.5 * (self.v ) ** 2) * self.dtm * self.path + (self.v)*np.sqrt(self.dtm)*self.z)\n",
    "        self.STP_optionPrice = self.PayOffPricertplus(self.S_Tplus)\n",
    "        self.STM_optionPrice = self.PayOffPricertminus(self.S_Tminus)\n",
    "        self.theta =-(self.STP_optionPrice-self.STM_optionPrice)/(self.Tp-self.Tm)\n",
    "        return self.theta\n",
    "    \n",
    "    def OptionPricer(self):\n",
    "        self.OptionPrice()\n",
    "        self.CallDelta()\n",
    "        self.OptionGamma()\n",
    "        self.Vega()\n",
    "        self.Theta()\n",
    "    \n",
    "    def Scenario_cal(self):\n",
    "        self.OptionPricer()\n",
    "        return self.S,self.S_optionPrice,self.callDelta,self.Gamma,self.vega,self.theta\n",
    "\n",
    "class snow(monte_carlo):\n",
    "    def __init__(self,S,HHigh,HLow,KLow,T,rCoupon,rMaturity,kiObservationDates,koObservationDates,r,b,v,N,numSims,ds):\n",
    "        super().__init__(S, T, r, v, N,ds,numSims)\n",
    "        self.HHigh = HHigh\n",
    "        self.HLow = HLow\n",
    "        self.KLow = KLow\n",
    "        # 敲出票息\n",
    "        self.rCoupon = rCoupon\n",
    "        # 到期票息\n",
    "        self.rMaturity = rMaturity\n",
    "        # 敲入观察日\n",
    "        self.kiObservationDates = kiObservationDates\n",
    "        # 敲入状态\n",
    "        self.koDate=0\n",
    "        # 敲出观察日\n",
    "        self.koObservationDates = koObservationDates\n",
    "        self.b = b\n",
    "\n",
    "class sepreate(snow):\n",
    "    def __init__(self, S, HHigh, HLow, KLow, T, rCoupon, rMaturity, kiObservationDates, koObservationDates, r, b, v, N, numSims, ds):\n",
    "        super().__init__(S, HHigh, HLow, KLow, T, rCoupon, rMaturity, kiObservationDates, koObservationDates, r, b, v, N, numSims, ds)    \n",
    "\n",
    "    def SeperatePrice(self):\n",
    "        self.knockOutPrice,self.doubleNoTouchPrice,self.knockinPrice=SeperatePrice_func(self.ST,self.koObservationDates,self.kiObservationDates\n",
    "        ,self.HHigh,self.HLow,self.rCoupon,self.N,self.r,self.rMaturity,self.T\n",
    "        ,self.KLow,self.numSims,self.dt)\n",
    "        return self.knockOutPrice,self.doubleNoTouchPrice,self.knockinPrice"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 3,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "100\n"
     ]
    },
    {
     "ename": "NameError",
     "evalue": "name 'sepreate' is not defined",
     "output_type": "error",
     "traceback": [
      "\u001b[1;31m---------------------------------------------------------------------------\u001b[0m",
      "\u001b[1;31mNameError\u001b[0m                                 Traceback (most recent call last)",
      "\u001b[1;32m<ipython-input-3-2d7ff9e91f48>\u001b[0m in \u001b[0;36m<module>\u001b[1;34m\u001b[0m\n\u001b[0;32m     22\u001b[0m     \u001b[0mprint\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mS\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m     23\u001b[0m     \u001b[0mds\u001b[0m \u001b[1;33m=\u001b[0m \u001b[0mS\u001b[0m \u001b[1;33m*\u001b[0m \u001b[1;36m0.01\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[1;32m---> 24\u001b[1;33m     snowBall = sepreate(S=S, HHigh=HHigh, HLow=HLow, KLow=KLow, T=T, rCoupon=rCoupon,\n\u001b[0m\u001b[0;32m     25\u001b[0m                             \u001b[0mrMaturity\u001b[0m\u001b[1;33m=\u001b[0m\u001b[0mrMaturity\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mkiObservationDates\u001b[0m\u001b[1;33m=\u001b[0m\u001b[0mkiObservationDates\u001b[0m\u001b[1;33m,\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m     26\u001b[0m                             \u001b[0mkoObservationDates\u001b[0m\u001b[1;33m=\u001b[0m\u001b[0mkoObservationDates\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mr\u001b[0m\u001b[1;33m=\u001b[0m\u001b[0mr\u001b[0m\u001b[1;33m,\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n",
      "\u001b[1;31mNameError\u001b[0m: name 'sepreate' is not defined"
     ]
    }
   ],
   "source": [
    "koObservationDates = np.array([30*(i+1) for i in range(12)])\n",
    "kiObservationDates = np.array([i for i in range(360)])\n",
    "S_list = [100+i for i in range(1)]\n",
    "HLow = 80\n",
    "HHigh = 103\n",
    "KLow = 100\n",
    "rCoupon = 0.1\n",
    "rMaturity = 0.1\n",
    "\n",
    "# 交易日个数\n",
    "N = 361\n",
    "T = 1\n",
    "r = 0.025\n",
    "b = 0\n",
    "v =0.1\n",
    "\n",
    "numSims =int(5e5)\n",
    "\n",
    "#多个行权价测试delta和gamma曲线\n",
    "df_list=[]\n",
    "for S in S_list:\n",
    "    print(S)\n",
    "    ds = S * 0.01\n",
    "    snowBall = sepreate(S=S, HHigh=HHigh, HLow=HLow, KLow=KLow, T=T, rCoupon=rCoupon,\n",
    "                            rMaturity=rMaturity, kiObservationDates=kiObservationDates,\n",
    "                            koObservationDates=koObservationDates, r=r,\n",
    "                            b=b, v=v, N=N, numSims=numSims, ds=ds)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 10,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "100\n"
     ]
    },
    {
     "ename": "KeyboardInterrupt",
     "evalue": "",
     "output_type": "error",
     "traceback": [
      "\u001b[1;31m---------------------------------------------------------------------------\u001b[0m",
      "\u001b[1;31mKeyboardInterrupt\u001b[0m                         Traceback (most recent call last)",
      "\u001b[1;32m<ipython-input-10-942d198349ce>\u001b[0m in \u001b[0;36m<module>\u001b[1;34m\u001b[0m\n\u001b[0;32m     29\u001b[0m                             \u001b[0mrMaturity\u001b[0m\u001b[1;33m=\u001b[0m\u001b[0mrMaturity\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mkiObservationDates\u001b[0m\u001b[1;33m=\u001b[0m\u001b[0mkiObservationDates\u001b[0m\u001b[1;33m,\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m     30\u001b[0m                             \u001b[0mkoObservationDates\u001b[0m\u001b[1;33m=\u001b[0m\u001b[0mkoObservationDates\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mr\u001b[0m\u001b[1;33m=\u001b[0m\u001b[0mr\u001b[0m\u001b[1;33m,\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[1;32m---> 31\u001b[1;33m                             b=b, v=v, N=N, numSims=numSims, ds=ds)\n\u001b[0m\u001b[0;32m     32\u001b[0m     \u001b[0mknockOutPrice\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mdoubleNoTouchPrice\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mknockinPrice\u001b[0m\u001b[1;33m=\u001b[0m\u001b[0msnowBall\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mSeperatePrice\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m     33\u001b[0m     \u001b[0mdf\u001b[0m\u001b[1;33m=\u001b[0m\u001b[0mpd\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mSeries\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mindex\u001b[0m\u001b[1;33m=\u001b[0m\u001b[1;33m[\u001b[0m\u001b[1;34m'标的价格'\u001b[0m\u001b[1;33m,\u001b[0m\u001b[1;34m'期权现价'\u001b[0m\u001b[1;33m,\u001b[0m\u001b[1;34m'敲出'\u001b[0m\u001b[1;33m,\u001b[0m\u001b[1;34m'没敲入没敲出'\u001b[0m\u001b[1;33m,\u001b[0m\u001b[1;34m'敲入没敲出'\u001b[0m\u001b[1;33m]\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mdtype\u001b[0m\u001b[1;33m=\u001b[0m\u001b[1;34m'float'\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n",
      "\u001b[1;32m<ipython-input-9-ddcc94fe56ef>\u001b[0m in \u001b[0;36m__init__\u001b[1;34m(self, S, HHigh, HLow, KLow, T, rCoupon, rMaturity, kiObservationDates, koObservationDates, r, b, v, N, numSims, ds)\u001b[0m\n\u001b[0;32m    162\u001b[0m \u001b[1;32mclass\u001b[0m \u001b[0msepreate\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0msnow\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m:\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m    163\u001b[0m     \u001b[1;32mdef\u001b[0m \u001b[0m__init__\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mself\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mS\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mHHigh\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mHLow\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mKLow\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mT\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mrCoupon\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mrMaturity\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mkiObservationDates\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mkoObservationDates\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mr\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mb\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mv\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mN\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mnumSims\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mds\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m:\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[1;32m--> 164\u001b[1;33m         \u001b[0msuper\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0m__init__\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mS\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mHHigh\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mHLow\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mKLow\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mT\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mrCoupon\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mrMaturity\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mkiObservationDates\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mkoObservationDates\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mr\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mb\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mv\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mN\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mnumSims\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mds\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0m\u001b[0;32m    165\u001b[0m \u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m    166\u001b[0m     \u001b[1;32mdef\u001b[0m \u001b[0mSeperatePrice\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mself\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m:\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n",
      "\u001b[1;32m<ipython-input-9-ddcc94fe56ef>\u001b[0m in \u001b[0;36m__init__\u001b[1;34m(self, S, HHigh, HLow, KLow, T, rCoupon, rMaturity, kiObservationDates, koObservationDates, r, b, v, N, numSims, ds)\u001b[0m\n\u001b[0;32m    144\u001b[0m \u001b[1;32mclass\u001b[0m \u001b[0msnow\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mmonte_carlo\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m:\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m    145\u001b[0m     \u001b[1;32mdef\u001b[0m \u001b[0m__init__\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mself\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mS\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mHHigh\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mHLow\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mKLow\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mT\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mrCoupon\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mrMaturity\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mkiObservationDates\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mkoObservationDates\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mr\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mb\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mv\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mN\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mnumSims\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mds\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m:\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[1;32m--> 146\u001b[1;33m         \u001b[0msuper\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0m__init__\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mS\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mT\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mr\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mv\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mN\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mds\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mnumSims\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0m\u001b[0;32m    147\u001b[0m         \u001b[0mself\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mHHigh\u001b[0m \u001b[1;33m=\u001b[0m \u001b[0mHHigh\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m    148\u001b[0m         \u001b[0mself\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mHLow\u001b[0m \u001b[1;33m=\u001b[0m \u001b[0mHLow\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n",
      "\u001b[1;32m<ipython-input-9-ddcc94fe56ef>\u001b[0m in \u001b[0;36m__init__\u001b[1;34m(self, S, T, r, v, N, ds, numSims)\u001b[0m\n\u001b[0;32m     68\u001b[0m         \u001b[0mself\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mnumSims\u001b[0m \u001b[1;33m=\u001b[0m \u001b[0mnumSims\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m     69\u001b[0m         \u001b[0mself\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mdt\u001b[0m \u001b[1;33m=\u001b[0m \u001b[0mfloat\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mT\u001b[0m \u001b[1;33m/\u001b[0m \u001b[0mN\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[1;32m---> 70\u001b[1;33m         \u001b[0mself\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mPathGeneration\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0m\u001b[0;32m     71\u001b[0m \u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m     72\u001b[0m     \u001b[1;32mdef\u001b[0m \u001b[0mPathGeneration\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mself\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m:\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n",
      "\u001b[1;32m<ipython-input-9-ddcc94fe56ef>\u001b[0m in \u001b[0;36mPathGeneration\u001b[1;34m(self)\u001b[0m\n\u001b[0;32m     77\u001b[0m         \u001b[0mpath\u001b[0m\u001b[1;33m=\u001b[0m\u001b[0mnp\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mtile\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mnp\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0marange\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;36m0\u001b[0m\u001b[1;33m,\u001b[0m\u001b[0mself\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mN\u001b[0m\u001b[1;33m,\u001b[0m\u001b[1;36m1\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m,\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mself\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mnumSims\u001b[0m\u001b[1;33m,\u001b[0m\u001b[1;36m1\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m     78\u001b[0m         \u001b[0mself\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mpath\u001b[0m\u001b[1;33m=\u001b[0m\u001b[0mpath\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[1;32m---> 79\u001b[1;33m         \u001b[0mself\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mST\u001b[0m\u001b[1;33m=\u001b[0m\u001b[0mself\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mS\u001b[0m\u001b[1;33m*\u001b[0m\u001b[0mnp\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mexp\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mself\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mr\u001b[0m\u001b[1;33m-\u001b[0m\u001b[1;36m0.5\u001b[0m\u001b[1;33m*\u001b[0m\u001b[0mself\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mv\u001b[0m\u001b[1;33m**\u001b[0m\u001b[1;36m2\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m*\u001b[0m\u001b[0mself\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mdt\u001b[0m\u001b[1;33m*\u001b[0m\u001b[0mself\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mpath\u001b[0m\u001b[1;33m+\u001b[0m\u001b[0mself\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mv\u001b[0m\u001b[1;33m*\u001b[0m\u001b[0mnp\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0msqrt\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mself\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mdt\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m*\u001b[0m\u001b[0mself\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mz\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0m\u001b[0;32m     80\u001b[0m         \u001b[1;32mreturn\u001b[0m \u001b[0mself\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mST\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m     81\u001b[0m \u001b[1;33m\u001b[0m\u001b[0m\n",
      "\u001b[1;31mKeyboardInterrupt\u001b[0m: "
     ]
    }
   ],
   "source": [
    "import datetime as dt\n",
    "import pandas as pd\n",
    "\n",
    "start=dt.datetime.now()\n",
    "koObservationDates = np.array([30*(i+1) for i in range(12)])\n",
    "kiObservationDates = np.array([i for i in range(360)])\n",
    "S_list = [100+i for i in range(1)]\n",
    "HLow = 80\n",
    "HHigh = 103\n",
    "KLow = 100\n",
    "rCoupon = 0.1\n",
    "rMaturity = 0.1\n",
    "\n",
    "# 交易日个数\n",
    "N = 361\n",
    "T = 1\n",
    "r = 0.025\n",
    "b = 0\n",
    "v =0.1\n",
    "\n",
    "numSims =int(5e5)\n",
    "\n",
    "#多个行权价测试delta和gamma曲线\n",
    "df_list=[]\n",
    "for S in S_list:\n",
    "    print(S)\n",
    "    ds = S * 0.01\n",
    "    snowBall = sepreate(S=S, HHigh=HHigh, HLow=HLow, KLow=KLow, T=T, rCoupon=rCoupon,\n",
    "                            rMaturity=rMaturity, kiObservationDates=kiObservationDates,\n",
    "                            koObservationDates=koObservationDates, r=r,\n",
    "                            b=b, v=v, N=N, numSims=numSims, ds=ds)\n",
    "    knockOutPrice,doubleNoTouchPrice,knockinPrice=snowBall.SeperatePrice()\n",
    "    df=pd.Series(index=['标的价格','期权现价','敲出','没敲入没敲出','敲入没敲出'],dtype='float')\n",
    "    df['标的价格']=S\n",
    "    df['期权现价']=knockOutPrice+doubleNoTouchPrice+knockinPrice\n",
    "    df['敲出']=knockOutPrice\n",
    "    df['没敲入没敲出']= doubleNoTouchPrice\n",
    "    df['敲入没敲出']=knockinPrice\n",
    "    df_list.append(df)\n",
    "\n",
    "result=pd.concat(df_list,axis=1).T\n",
    "end=dt.datetime.now()\n",
    "elapsed=(end-start).total_seconds()\n",
    "result.to_excel('result.xlsx')\n",
    "print('计算消耗:{:.2f}秒'.format(elapsed))"
   ]
  }
 ],
 "metadata": {
  "kernelspec": {
   "display_name": "Python 3",
   "language": "python",
   "name": "python3"
  },
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 3
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython3",
   "version": "3.7.3"
  }
 },
 "nbformat": 4,
 "nbformat_minor": 2
}
